package com.guo.mixframe.framework.utils

import com.guo.mixframe.framework.log.LogPrint
import io.protostuff.LinkedBuffer
import io.protostuff.ProtobufIOUtil
import io.protostuff.Schema
import io.protostuff.runtime.RuntimeSchema
import java.lang.Exception

/**
 * @author  gx
 * @description
 */
object ProtobufUtils {

  fun <T> byteToBean(data:ByteArray,clazz: Class<T>) : T {
    val schema = RuntimeSchema.getSchema(clazz)
    val bean = schema.newMessage()
    ProtobufIOUtil.mergeFrom(data,bean,schema)
    return bean
  }


  /**
   * 序列化pb
   */
  fun <T> bean2Byte(bean: T): ByteArray {
    return try {
      val buffer = applicationBuffer
      val schema = RuntimeSchema.getSchema(bean!!.javaClass) as Schema<T>
      ProtobufIOUtil.toByteArray(bean, schema, buffer)
    } catch (e: Exception) {
      LogPrint.logger.error("catch exception on bean2Byte. class " + bean!!.javaClass.name)

      throw e
    }
  }

  private const val bufferSize = 1024 * 64

  private val localBuffer: ThreadLocal<LinkedBuffer> = object : ThreadLocal<LinkedBuffer>() {
    public override fun initialValue(): LinkedBuffer {
      return LinkedBuffer.allocate(bufferSize)
    }
  }

  /**
   * 取buff, 线程安全
   */
  private val applicationBuffer: LinkedBuffer
    get() = localBuffer.get().clear()

}
